package both.map.mapModel.unitTests;

import org.junit.Before;
import org.junit.Test;
import both.map.mapModel.*;
import both.map.*;
import java.awt.Dimension;
import java.util.ArrayList;
import junit.framework.Assert;

public class MapTest {
	private static final Dimension chunkSize = new Dimension(20,20);
	private static final Dimension chunkGridSize = new Dimension(2,2);
	
	private ModelMap map;
	private ModelMap update;
	private ModelMap recipient;
	
	@Before
	public void setUp() throws Exception {
		map = new ModelMap(chunkSize, chunkGridSize);
		ModelChunk chunk = new ModelChunk(chunkSize);
		map.updateChunk(0, 0, chunk);
		recipient = new ModelMap(chunkSize, chunkGridSize);
	}

	@Test
	public void testMapDimension() {
		try {
			new ModelMap(chunkSize, chunkGridSize);
		} catch (Exception e) {
			Assert.fail(e.toString());
		}
	}

	@Test
	public void testUpdateChunk() {
		ModelChunk updateChunk = new ModelChunk(chunkSize);
		TerrainCell tc = (TerrainCell) updateChunk.getLayer(LayerType.TERRAIN).getCell(1,1);
		Assert.assertNotSame(tc, map.getChunkAt(0,0).getLayer(LayerType.TERRAIN).getCell(1,1));
		map.updateChunk(0,0,updateChunk);
		Assert.assertSame(tc, map.getChunkAt(0,0).getLayer(LayerType.TERRAIN).getCell(1,1));
	}
	
	@Test
	public void testGetChunksize() {
		Assert.assertEquals(new Dimension(20,20), map.getChunksize());
		Dimension x = new Dimension(4,4);
		ModelMap m = new ModelMap(x, chunkGridSize);
		Assert.assertEquals(x, m.getChunksize());
	}

	@Test
	public void testGetActiveChunksCoordinates() {
		Assert.assertEquals(1,map.getActiveChunksCoordinates().size());
		ArrayList<Dimension> coords = new ArrayList<Dimension>();
		coords.add(new Dimension(0,0));
		Assert.assertEquals(coords, map.getActiveChunksCoordinates());
		coords.add(new Dimension(0,1));
		map.updateChunk(0,1,new ModelChunk(chunkSize));
		Assert.assertEquals(coords, map.getActiveChunksCoordinates());
	}

	@Test
	public void testUpdate() {
		map = new ModelMap(chunkSize, chunkGridSize);
		map.grabUpdate();
		Assert.assertNull(map.grabUpdate());
		map.updateChunk(0,0, new ModelChunk(chunkSize));
		TerrainCell tc = (TerrainCell) map.getChunkAt(0,0).getLayer(LayerType.TERRAIN).getCell(0,0);
		tc.reassignTerrain(TerrainType.mud);
		update = map.grabUpdate();
		// should be null - the terrain type was updated, but that isn't visible.
		Assert.assertNull(update);
		VisibilityCell vc = (VisibilityCell) map.getChunkAt(0,0).getLayer(LayerType.VISIBILITY).getCell(0,0);
		vc.setVisibility(true,true);
		update = map.grabUpdate();
		Assert.assertNotNull(update);
		try {
			recipient.applyUpdate(update);
		} catch (UpdateStatusException e) {
			System.out.println(e);
			Assert.fail();
		}
		Assert.assertNotNull(recipient.grabUpdate());
		update = map.grabUpdate();
		Assert.assertNull(update);
		TerrainCell originalTC = (TerrainCell) map.getChunkAt(0,0).getLayer(LayerType.TERRAIN).getCell(0,0);
		TerrainCell recipientTC = (TerrainCell) recipient.getChunkAt(0,0).getLayer(LayerType.TERRAIN).getCell(0,0);
		Assert.assertEquals(originalTC.getTerrainType(),recipientTC.getTerrainType());
	}

}
